package view;

import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.image.BufferedImage;
import javax.swing.*;
import model.Player;
import control.GameControl;
import control.IFieldsControl;
import control.IPlayerControl;
import java.util.*;
import java.util.regex.Pattern;

/**
 * This Class contains the board, player images and 
 * all other drawing related stuff
 * @author Thomas
 *
 */

public class Board extends JPanel 
{
	private static final long serialVersionUID = 1L;
	//private Image boardImage, backgrd;
	private ArrayList<ImageIcon> imageList;
	private GameControl gControl;
	private ImageIcon boardImage, backgrd;
	private BufferedImage bufBack = new BufferedImage(1000, 1000, BufferedImage.TYPE_INT_RGB);
	private BufferedImage houseBuffer = new BufferedImage(655, 655, BufferedImage.TRANSLUCENT);
	private ImageIcon house = ImageCreator.createImageIcon("Images/house.png");
	private ImageIcon hotel = ImageCreator.createImageIcon("Images/hotel.png");
	private ImageIcon hypothek = ImageCreator.createImageIcon("Images/hypothek.png");
	private JButton menuButton;
	private JButton helpButton;
	private String time = "";
	private ArrayList<Player> pl;
	
	public Board(GameControl gc, String boardType)
	{
		gControl = gc;
		pl = gControl.getPlayerControl().getPlayerList();
		imageList = new ArrayList<ImageIcon>();
		
		for(int i = 0; i < pl.size(); i++)
		{
			imageList.add(gc.getPlayerControl().getPlayerImage(i));
		}
		
		if(boardType.equalsIgnoreCase("originalBoard"))
			boardImage = ImageCreator.createImageIcon("Images/boards/FELD_blank.png");
		else if(boardType.equalsIgnoreCase("swBoard"))
			boardImage = ImageCreator.createImageIcon("Images/boards/FELD_sw.png");
		else if(boardType.equalsIgnoreCase("simpBoard"))
			boardImage = ImageCreator.createImageIcon("Images/boards/FELD_simp.png");
		
		backgrd = ImageCreator.createImageIcon("Images/pattern/background.png");
		
		Graphics2D imageG = (Graphics2D) bufBack.getGraphics();
		imageG.drawImage(backgrd.getImage(), 0,0, this);
		imageG.drawImage(boardImage.getImage(), 0, 0, this);
		
		menuButton = new JButton("Menu");
		menuButton.setFont(new Font("sansserif",Font.BOLD,14));
		menuButton.setContentAreaFilled(false);
		menuButton.setBorder(BorderFactory.createEmptyBorder());
		menuButton.setFocusable(false);
		menuButton.setOpaque(false);
		menuButton.setBounds(260, 340, 90, 100);
		menuButton.setOpaque(false);
		menuButton.setCursor(Cursor.getPredefinedCursor(Cursor.HAND_CURSOR));
		menuButton.addActionListener(new ActionListener()
		{
			public void actionPerformed(ActionEvent event)
			{
				GameControl.getControlInstance().showGameMenu(); //call the game menu from GC
			}
		});
		
		helpButton = new JButton("Hilfe");
		helpButton.setFont(new Font("sansserif",Font.BOLD,14));
		helpButton.setContentAreaFilled(false);
		helpButton.setBorder(BorderFactory.createEmptyBorder());
		helpButton.setFocusable(false);
		helpButton.setOpaque(false);
		helpButton.setBounds(180, 365, 80, 80);
		helpButton.setOpaque(false);
		helpButton.setCursor(Cursor.getPredefinedCursor(Cursor.HAND_CURSOR));
		helpButton.addActionListener(new ActionListener()
		{
			public void actionPerformed(ActionEvent event)
			{
				new Help(); //call the help
			}
		});
		
		this.setLayout(null);
		this.add(menuButton);
		this.add(helpButton);
	}
	/**
	 * method responsible for drawing everything in the game
	 */
	public void paint(Graphics g)
	{
		Graphics2D g2D = (Graphics2D) g;
		super.paint(g2D);
		
		String pattern = "[/]";
		Pattern splitter = Pattern.compile(pattern);
		String[] result;
		String newPath;
		
		g2D.drawImage(bufBack, 0, 0,this);

		for(int i = 0; i < imageList.size(); i++)
		{
			result = splitter.split(imageList.get(i).toString());
			newPath = "Images/figures/small_"+result[result.length-1];
			g2D.drawImage(ImageCreator.createImageIcon(newPath).getImage(), gControl.getPlayerControl().getX(i), gControl.getPlayerControl().getY(i), this);
		}
		
		g2D.drawImage(houseBuffer, 0, 0, this);
	
		g2D.setFont(new Font("sansserif", Font.BOLD, 12));
		g2D.drawString(time, 115, 175);
		
		super.setOpaque(false);	//needed so that the button is above the background image
		
		
		
	}
	
	/**
	 * method that prepares the buffered images on 
	 * which the houses, hotels and mortgages 
	 * will be painted on
	 */
	public void drawHouses()
	{
		houseBuffer =  new BufferedImage(655, 655, BufferedImage.TRANSLUCENT);
		Graphics2D imageG = (Graphics2D) houseBuffer.createGraphics();
		
		
		IFieldsControl fieldControl = GameControl.getControlInstance().getFieldsControl();
		
		int[][][] test = HouseCoordinates.houseCoordinates;
		
		ArrayList<Integer> allFields = fieldControl.getFieldList("all");
		
		int[] streets = new int[test.length];
		
		//create an array with those fields that can be built on
		int count = 0;
		for(int i=0;i<allFields.size();i++)
		{
			if(fieldControl.getType(allFields.get(i)).equals("street") 
					|| fieldControl.getType(allFields.get(i)).equals("plant")
					|| fieldControl.getType(allFields.get(i)).equals("station"))
			{
				streets[count] = allFields.get(i);

				count++;
			}
		}
	
		//do the necessary drawing
		int amount=0;
		for(int i = 0; i < streets.length; i++)
		{
			boolean hasHypothek = false;
			amount = fieldControl.getHouses(streets[i]);
			
			IPlayerControl pc = GameControl.getControlInstance().getPlayerControl();
			
			for(int l = 0; l < pc.getNumberOfPlayers(); l++)
			{
				if(pc.hasMortgage(streets[i], l))
					hasHypothek = true;
			}

			//draw hotel
			if(amount > 4)
				imageG.drawImage(hotel.getImage(), test[i][1][0], test[i][1][1], this);
			//or draw certain amount of houses
			else if(amount <= 4)
			{
				for(int j = 0; j < amount; j++)
					imageG.drawImage(house.getImage(), test[i][j + 1][0], test[i][j + 1][1], this);
			}
			if(hasHypothek == true)
			{
				imageG.drawImage(hypothek.getImage(), test[i][3][0], test[i][3][1], this);
			}
			
		}		
				
		this.repaint();
	
	}
	
	/**
	 * update the list of images
	 */
	public void updateImageList()
	{
		//first, clear the list
		imageList.clear();
		
		//refill the list
		for(int i = 0; i < pl.size(); i++)
		{
			imageList.add(GameControl.getControlInstance().getPlayerControl().getPlayerImage(i));
		}
	}
	
	/**
	 * method that updates the game time onscreen
	 * @param gameTime the gametime to be updated
	 */
	public void updateTime(String gameTime)
	{
		this.time = "Zeit: " + gameTime;
		
		this.repaint();
	}
}
